<?php
require_once '../common/RootPath.php';

//$rootPath = RootPath::getRootPath();

RootPath::importPath("common/FileUtil.php");
RootPath::importPath("common/DateHelper.php");
RootPath::importPath("common/ConverterUtils.php");
RootPath::importPath("common/UniqueUtils.php");

class XmlUtils
{
    private $filePathName;//相对路径文件名称

    public function __construct($fileName)
    {

        //global $rootPath;

        //$this->filePathName = $rootPath . $fileName;
        $this->filePathName = $fileName;


        try {

            if (!FileUtil::exists($this->filePathName)) {
                FileUtil::createFile($this->filePathName);
                //存在
                // 创建XML内容
                $xml = new SimpleXMLElement('<?xml version="1.0" encoding="UTF-8"?><root></root>');

                $xml->saveXML($this->filePathName);
                //echo "文件创建成功";
            } else {

                libxml_use_internal_errors(true);  // 启用内部错误处理

                $xml = simplexml_load_file($this->filePathName);

                if ($xml === false) {
                    echo "XML格式错误：\n";
                    // 清空文件内容
                    if (file_put_contents($this->filePathName, '') !== false) {
                        echo "文件内容已清空！";
                        $xml = new SimpleXMLElement('<?xml version="1.0" encoding="UTF-8"?><root></root>');

                        $xml->saveXML($this->filePathName); //$xml-asXML()一样
                    } else {
                        echo "清空文件内容时出错！";
                    }
                    foreach (libxml_get_errors() as $error) {
                        echo $error->message . "\n";
                    }
                } else {
                    //echo "XML格式正确！\n";
                }


            }
        } catch (Exception $e) {
            echo "错误：" . $e->getMessage();
        }
    }

    //如果存在则更改，否则新建,适合验证码 array $params
    public function existsChange(array $params)
    {
        $name = array_key_first($params);
        $val = $params[$name];

        // 加载 XML 文件或字符串
       $xml = simplexml_load_file($this->filePathName);// XML 文件路径

        // 将 XML 转换为 DOMDocument 以便修改
        $dom = new DOMDocument();
        $dom->preserveWhiteSpace = false;
        $dom->formatOutput = true;
        $dom->loadXML($xml->asXML());

        // 查找所有的 <item> 节点
        $xpath = new DOMXPath($dom);
        $items = $xpath->query('//item');

        $found = false;
        foreach ($items as $item) {
            $sid = $item->getElementsByTagName('sid')->item(0)->nodeValue;
            if ($sid === UniqueUtils::getSignSid()) {
                // 如果找到 name=admin 的节点，修改其他字段
                $item->getElementsByTagName($name)->item(0)->nodeValue = $val;
                $item->getElementsByTagName('time')->item(0)->nodeValue = DateHelper::now();
                $found = true;
            }
        }

        if (!$found) {
            // 如果未找到 name=admin 的节点，添加新数据
            $newItem = $dom->createElement('item');
            $newCode = $dom->createElement($name, $val);
            $newSid = $dom->createElement('sid', UniqueUtils::getSignSid());
            $newTime = $dom->createElement('time', DateHelper::now());

            $newItem->appendChild($newCode);
            $newItem->appendChild($newSid);
            $newItem->appendChild($newTime);
            $dom->documentElement->appendChild($newItem);
        }

        // 保存修改后的 XML
        $dom->save($this->filePathName);

//        echo "操作完成，结果已保存到 $this->filePathName";
    }

    //根据参数条件筛选
    public function findByParam($paramName)
    {
        $read = $this->read();
        return array_map(function ($item) use ($paramName) {
            return $item[$paramName];
        }, $read);

    }


    // 根据特定条件筛选
    public function findByFiltering($conditions = [])
    {
        try {

            if (!empty($conditions)) {

                $filteringItems = [];
                foreach ($conditions as $keys => $values) {
                    if (strpos($keys, 'code') !== false) {
                        $filteringItems[$keys] = $values;
                    }
                }

                $searchName = array_key_first($filteringItems);

                // 加载 XML 数据
                $xml = simplexml_load_file($this->filePathName);

                /*  echo $filteringItems[$searchName];
                  echo  $searchName;*/

                $result = $xml->xpath("//item[$searchName='$filteringItems[$searchName]']");
                return $result;

            }


        } catch (Exception $e) {
            echo "错误：" . $e->getMessage();
        }

    }

    //过期删除 minute分钟
    public function expireDelete($minute)
    {
        try {
            $xml = simplexml_load_file($this->filePathName);

            // 检查文件是否成功加载
            if ($xml === false) {
                echo "Error loading XML file.";
            } else {
                // 获取当前时间
                $currentTime = DateHelper::now();

                $nodesToDelete = [];
                // 遍历节点并检查时间差
                foreach ($xml->item as $item) {

                    //从xml取出时间
                    $itemTime = $item->time;

                    //$itemTime记录的时间，$currentTime当前时间
                    $interval = DateHelper::getDiffInMinutes($itemTime, $currentTime);

                    // 如果时间差大于 60 分钟，删除节点
                    if ($interval > $minute) {
                        $nodesToDelete[] = $item;  //满足条件放入数组
                    }
                }

                foreach ($nodesToDelete as $item){
                    // 通过 DOM 删除节点
                    $dom = dom_import_simplexml($item);
                    $dom->parentNode->removeChild($dom);
                }
                // 输出更新后的 XML
               $xml->asXML($this->filePathName);
            }
        } catch (Exception $e) {
            echo "错误：" . $e->getMessage();
        }
    }

    //读取全部
    public function read()
    {
        try {
            // 读取 XML 文件并加载为 SimpleXMLElement 对象
            $xml = simplexml_load_file($this->filePathName);

            // 检查文件是否成功加载
            if ($xml === false) {
                echo "Error loading XML file.";
//                throw new Exception("Error: Failed load XML file.");
            } else {
                // 遍历所有的 元素并输出信息
                $data = [];
                foreach ($xml->item as $node) {
                    $items = [];
                    foreach ($node as $key => $value) {
                        $items[$key] = (string)$value;
                    }
                    $data[] = $items;
                }
                return $data;
            }

        } catch (Exception $e) {
            echo "错误：" . $e->getMessage();
        }
    }

    //创建文件
    public function create(array $params)
    {
        try {
            $xml = simplexml_load_file($this->filePathName);
            //在根元素下面创建一个标签，名字是line
            $child = $xml->addChild('item');

            if (is_array($params) && !empty($params)) {
                foreach ($params as $keys => $values) {
                    $child->addChild($keys, $values);
                }
                $xml->saveXML($this->filePathName);
            } else {
                echo "错误：params参数不能为空";
            }
        } catch (Exception $e) {
            echo "错误：" . $e->getMessage();
        }

    }


    public function update(array $params)
    {
        $xml = simplexml_load_file($this->filePathName);
        //在根元素下面创建一个标签，名字是line

        $removedItems = [];
        foreach ($params as $keys => $values) {
            //echo $keys .':' .$values."\n";
            if (strpos($keys, 'id') !== false) {

                $removedItems[$keys] = $values;
            }
        }

        $values = array_values($removedItems);
        $selectID = $values[0];

        $line = $xml->item[(int)$selectID];

        if (!empty($line)) {
            $array = ConverterUtils::objectToArray($line);

            // 把$params赋值$array，相同元素
            foreach ($array as $key => $value) {
                if (array_key_exists($key, $params)) {
                    $array[$key] = $params[$key];
                }
            }


            //数组转xml
            function arrayToXml($data, &$xmlData)
            {
                foreach ($data as $key => $value) {
                    // 如果键是数字，用 'item' 代替
                    if (is_numeric($key)) {
                        $key = 'item' . $key;
                    }
                    // 如果值是数组，递归处理
                    if (is_array($value)) {
                        $subnode = $xmlData->addChild($key);
                        arrayToXml($value, $subnode);
                    } else {
                        $xmlData->addChild($key, htmlspecialchars($value));
                    }
                }
            }

            $child = $xml->addChild('item');
            arrayToXml($array, $child);

            //将xml转为字符串
            //先删除后添加
            unset($xml->item[(int)$selectID]);
            echo $xml->saveXML($this->filePathName);
        } else {
            echo "not data";
        }

    }

    //删除
    public function delete($id)
    {
        $xml = simplexml_load_file($this->filePathName);
        //使用unset删除$xml中item索引为$id的那一条数据
        unset($xml->item[(int)$id]);
        $xml->saveXML($this->filePathName);

    }
}


//$xmlUtils = new XmlUtils('/data/code/css.xml');

//写
//$params = ['sid' => '0', 'username' => 'jiangmingz2', 'password' => 'aini1314', 'last_login_time' => DateHelper::now(), 'deleted' => '1'];
//$params = ['username' => 'jyh', 'password' => '123', 'last_login_time' => DateHelper::now(), 'deleted' => '1'];
//$xmlUtils->create($params);
//读
//$arr = $xmlUtils->read();
//$xmlUtils->delete("0");
//var_dump($arr);
//$xmlUtils->update($params);